// import data_manager from "./data_manager";

// import data_manager from "./data_manager";


const {ccclass, property} = cc._decorator;

//正式
// let ip: string = "https://api-dsd.cygame.cn/";
//测试
let ip: string = "https://dev-api-dsd.cygame.cn/";

//微信id
let wxid: string = null;

@ccclass
export class util{
    //单例
    private static _instace:util;
    public static get Instance():util {
        if(!this._instace)
            this._instace = new util;
        return this._instace;
    };

    public token: string = null;

    /**
     * 微信获取id并靠token登录
     * @param callback 获取token后执行的回调
     */
    getwxid(callback?) {
        let self = this;
        wx.login({
            success(res) {
                let bool: number = 0;
                wx.getSystemInfo({
                    success: function(ress){
                        let model:string = ress.model;
                        model = model.toUpperCase();
                        let iphone = "IPHONE"
                        let cunzai = model.indexOf(iphone);
                        if(cunzai == -1){
                            bool = 0;
                            console.log("安卓");
                        }else{
                            bool = 1;
                            console.log("苹果");
                        }
                    }
                });
                wxid = res.code;
                let url = "get_token";
                self.get_post(url, {ios: bool , code: wxid }, (res) => {
                    cc.sys.localStorage.setItem('token', res.data);
                    if(callback){
                        callback(res);
                    }
                });
            },
            fail(err){
                console.error("从微信拿code失败，3秒后重新来过",err);
                setTimeout(() => {
                    self.getwxid(callback);
                }, 3000);
            }
        })
    }

    private angin: number = 0;

    //用来检测短时间内是否有同一个接口被重复调用(1秒)
    schedule_function: number = null;
    game_url: string = null;

    /**
     * 后台请求
     * @param url 地址
     * @param params 传参
     * @param callback 回调
     * @param loading 是否显示读取框
     */
    get_post(url, params, callback?: Function, loading?: boolean) {
        //检测是否会同一时间重复调用一个接口
        // if(url != 'redpocket/redpocket_event'){
        //     if(this.game_url == null){
        //         this.game_url = url;
                
        //         clearTimeout(this.schedule_function);
        //         this.schedule_function = setTimeout(() => {
        //             this.game_url = null;
        //         }, 1000);
        //     }else{
        //         if(this.game_url == url){//同一秒调用了相同的接口！
        //             console.error("同一秒调用了同一个接口！",url);
        //             this.report_user(url);
        //             return;
        //         }else{
        //             this.game_url = url;
        //             clearTimeout(this.schedule_function);
        //             this.schedule_function = setTimeout(() => {
        //                 this.game_url = null;
        //             }, 1000); 
        //         }
        //     }
        // }

        //是否显示微信loading圈
        if(loading){
            wx.showLoading(true);
        }
        
        //网络请求
        let self = this;
        let urls = ip + url;
        wx.request({
            url: urls,
            data: params,
            method: 'POST',
            header: {
                'content-type': 'application/x-www-form-urlencoded' // 默认值
            },
            success: function (res) {
                self.angin = 0;
                wx.hideLoading();
                // data_manager.Instance.networks_data = res.data;
                if (res.data.code == '999') {
                    console.error("code过期，需要重新登录");
                    self.getwxid(() => {
                        if (callback) {
                            callback(res.data);
                        }
                    });
                }else if(res.data.code == '1'){
                    console.error("不可进行操作",url);
                } else if (res.data.code != '999') {
                    if (callback) {
                        callback(res.data);
                    }
                }
                return res.data;
            },
            fail: function (fail) {
                console.error(url,"网络请求失败，3秒后重新请求",fail);
                setTimeout(() => {
                    if(loading){
                        self.angin++;
                        if(self.angin >= 3){
                            console.error("网络连接失败");
                            self.angin = 0;
                            return
                        }
                    }

                    self.get_post(url,params,callback,loading);
                    
                }, 3000);
            },
            complete: function (complete) {
                wx.hideLoading();
            }
        })
    };

    /**
     * 上报错误信息
     */
    report_user(url){
        wx.request({
            url: (ip + "report_user"),
            data: {
                token: cc.sys.localStorage.getItem("token"),
                url: url,
            },
            method: 'POST',
            header: {
                'content-type': 'application/x-www-form-urlencoded' // 默认值
            },
        })
    }

    /**
     * 发送客服信息
     * @param From 消息来源
     * @param showMessageCard 是否出现卡片
     * @param title 卡片标题
     * @param path 卡片路径(不明，为空不会有问题)
     * @param img 卡片图片路径
     * @param success 成功回调
     * @param fail 失败回调
     */
    customer_service(From?: string, showMessageCard?: boolean,title?: string, path?: string, img?: string, success?: Function, fail?: Function){
        if(img == null){
            img = 'https://cdn.52nanm.com/shareimg.jpg';
        }
        if(cc.sys.platform === cc.sys.WECHAT_GAME){//微信环境
            wx.openCustomerServiceConversation({
                sessionFrom: From,
                showMessageCard: showMessageCard,
                sendMessageTitle: title,
                sendMessagePath: path,
                sendMessageImg: img,
                success(){
                    if(success){
                        success();
                    }
                },
                fail(){
                    if(fail){
                        fail();
                    }
                }
            })
        }else if(cc.sys.platform === cc.sys.DESKTOP_BROWSER){//模拟环境
            console.log("当前处于调试模式中,默认成功");
            if(success){
                success();
            }
        }else if(cc.sys.platform === cc.sys.UNKNOWN){//未知环境
            console.log("不知道当前环境，默认失败");
            if(fail){
                fail();
            }
        }
    }

    /**
     * 开启订阅信息
     */
    on_subscribe(tmplIds: string[],success?: Function, fail?: Function){
        if(cc.sys.platform === cc.sys.WECHAT_GAME){
            wx.subscribeAppMsg({
                subscribe: true,
                success(err){
                    if(success){
                        success();
                    }
                },
                fail(err){
                    if(err){
                        console.error(err.errCode,"订阅失败",err);
                    }
                    if(fail){
                        fail();
                    }
                }
            })
        }
        else if(cc.sys.platform === cc.sys.UNKNOWN){
            console.log("不知道当前环境，默认失败");
            if(fail){
                fail();
            }
        }
        else if(cc.sys.platform === cc.sys.DESKTOP_BROWSER){
            console.log("模拟器环境");
            if(success){
                success();
            }
        }
    }

    private share_show: Function = null;

    private share_hide: Function = null;

    private out_time: number = null;

    /**
     * 分享方法
     */
    share_function(callback?: Function){
        if(cc.sys.platform == cc.sys.WECHAT_GAME){
            if(callback){//有传入分享成功后进行输出的方法才会进入秒数判断
                wx.onHide(this.share_hide = () => {
                    console.log("微信分享的退出到后台判断");
                    this.out_time = Date.now();
                })
    
                wx.onShow(this.share_show = () => {
                    let now_time = Date.now();
                    let jingguo = Math.floor(now_time / 1000) - Math.floor(this.out_time / 1000);
                    if(jingguo >= 3000){//在分享界面超过3秒，判定成功
                        console.log('分享判定成功');
                        if(callback){
                            callback();
                        }
                    }else{
                        console.log('分享判定失败');
                    }
                    wx.offHide(this.share_hide);
                    wx.offShow(this.share_show);
                })
            }

            wx.shareAppMessage({
                title: '阳光牧场',
                imageUrl: 'https://cdn.52nanm.com/farm/shareImg.png',
                success: () => {//qq可用
                },
                complete: () => {
                },
            })
        }else{
            console.log("已经分享了");
        }
    }

    private wx_btn_login = null;

    /**
     * 授权用户信息并返回用户信息
     * @param callback 拿到信息后的回调
     * @param btn 用于登录遮挡的位置
     * @param on_btn_callback 点击了登录按钮并且拿到信息后要执行的方法(让方法不需要二次执行)
     */
    return_wx_userInfo(callback: Function, btn: cc.Node, on_btn_callback?: Function){
        let self = this;
        wx.getSetting({
            success(res) {
                if(res.authSetting['scope.userInfo']){//有授权用户信息
                    wx.getUserInfo({
                        success(res){
                            if(callback){
                                callback(res.userInfo);
                            }
                            return res.userInfo;
                        },
                        fail(res){
                            console.error("检测到有授权用户信息的情况下获取用户信息失败",res);
                            return false;
                        }
                    })
                }else{//没授权用户信息，新建授权按钮
                    let the_style = self.return_node_wx_poi(btn);
                    self.wx_btn_login = wx.createUserInfoButton({
                        type: 'image',
                        image: null,//'http://pic33.photophoto.cn/20141129/0034034877603068_b.jpg',//test
                        style: the_style,
                    })

                    self.wx_btn_login.onTap((res) => {
                        if(res.userInfo){//授权登录成功
                            if(callback){
                                callback(res.userInfo);
                            }
                            if(on_btn_callback){
                                on_btn_callback();
                            }
                            self.wx_btn_login.destroy();
                        }
                    });
                }
            },
            fail(res){
                console.error('获取用户设置失败',res);
                return false;
            }
        })
    }

    /**
     * 没有登录的情况下切换页面，删除登录按钮
     */
    destroy_wx_btn(){
        if(this.wx_btn_login){
            this.wx_btn_login.destroy();
        }
    }

    /**
     * 检测是否需要重新上报用户信息
     * 
     */
    update_userInfo(userInfo: any, callback?: Function){
        let data = cc.sys.localStorage.getItem('update_userInfo');
        if(data == null || data == ""){
            util.Instance.get_post('update_userinfo'
            ,{token: cc.sys.localStorage.getItem('token'), nickname: userInfo.nickName, avatarUrl: userInfo.avatarUrl}
            ,(res) => {
                if(callback){
                    callback();
                }
                data = true;
                cc.sys.localStorage.setItem(data,'update_userInfo');
            },true);
        }else{
            if(callback){
                callback();
            }
        }

    }

    /**
     * 传入一个节点，返回一个wx的屏幕坐标
     */
    return_node_wx_poi(node: cc.Node){
        let mobileheight = wx.getSystemInfoSync().screenHeight/cc.view.getDesignResolutionSize().height;

        let designSize = cc.view.getDesignResolutionSize();
        let worldPos = node.convertToWorldSpaceAR ( cc.v2 ( 0, 0 ) )
    
        let left = worldPos.x * mobileheight;
        let top = (designSize.height - worldPos.y) * mobileheight;
        let width = node.width * mobileheight;
        let height = node.height * mobileheight;
    
        left -= width * node.anchorX;
        top -= height * (1 - node.anchorY);
    
        return { left : left, top :top, width : width, height : height };
    }

    /**
     * 直接进行适配,修改sale，会导致其子节点也缩小(只针对高适配)
     * @param node 需要适配的节点
     */
    fit(node: cc.Node){
        let screenResolutionSize = cc.view.getVisibleSize()
        let designResolutionSize = cc.view.getDesignResolutionSize();
        
        // 根据变化比例调整主域物体
        let resultScale = screenResolutionSize.width / designResolutionSize.width
        resultScale = resultScale >= 1 ? 1 : resultScale;
        node.scale = resultScale;
    }

    return_fit(){
        let screenResolutionSize = cc.view.getVisibleSize()
        let designResolutionSize = cc.view.getDesignResolutionSize();
        
        // 根据变化比例调整主域物体
        let resultScale = screenResolutionSize.width / designResolutionSize.width;
        resultScale = resultScale >= 1 ? 1 : resultScale;
        return resultScale;
    }

    /**
     * 统一的弹窗显示方法(自带对齐)
     * @param node 弹窗的节点
     * @param callback 弹窗后执行的回调
     */
    Popup(node: cc.Node, callback?: Function){

        node.parent.active = true;

        node.scale = 0;

        let action1 = cc.scaleTo(0.7,this.return_fit());
        action1.easing(cc.easeBackInOut());
        let action2 = cc.callFunc(() => {
            if(callback){
                callback();
            }
        })
        let action3 = cc.sequence(action1,action2);
        cc.tween(node)
        .then(action3)
        .start()
    }

    /**
     * 统一的光圈转动方法
     * @param node 要出现的窗口(不包含背景)
     */
    autogiration(node: cc.Node){
        node.stopAllActions();
        let action1 = cc.rotateBy(3,360);
        let action2 = cc.repeatForever(action1);
        cc.tween(node)
        .then(action2)
        .start()
    }

    /**
     * 箭头抖动的效果
     */
    level_up_icon_move(node: cc.Node){
        node.scaleX = 1.15;
        node.scaleY = 0.75;
        let action1 = cc.moveBy(0.2,0,15);
        action1.easing(cc.easeOut(2.5));
        let action2 = cc.scaleTo(0.2,1,1);
        action2.easing(cc.easeOut(2.5));
        let action3 = cc.spawn(action1,action2);
        let action4 = cc.moveBy(0.2,0,-15);
        action4.easing(cc.easeIn(1));
        let action5 = cc.scaleTo(0.2,1.1,0.8);
        action5.easing(cc.easeIn(1));
        let action6 = cc.spawn(action4,action5);
        let action7 = cc.sequence(action3,action6);
        let action8 = cc.repeatForever(action7);
        cc.tween(node)
        .then(action8)
        .start()
    }

    /**
     * 统一的播放音效方法
     * @param node 要播放音效的节点(传递事件的节点，默认填this.node)
     * @param music 要播放的音效
     */
    play_sound(node: cc.Node, music: string){
        //点击音效
        let event = new cc.Event.EventCustom('music', true);
        event.setUserData(
            music,
        );
        node.dispatchEvent(event);
    }

    /**
     * 把number类型转换成带进制的string类型
     * @param number 要改变的数字
     * @param floor 是否向下取整的一位小数(否则向上取整)
     */
    label_to_string(number: number, floor?: boolean){
        let display:string[] = ['','k','m','b','t','q','Q','s','S','aa','bb','cc','dd','ee','ff','gg','hh','ii','jj','kk','ll','nn','mm'];
        let array_length = 0;
        for(let i = 0; i < display.length; i++){
            let number2 = number / 1000;
            if(number2 < 1){
                if(floor == true){
                    number = Math.floor(number * 10) / 10;
                }else{
                    number = Math.ceil(number * 10) / 10;
                }
                break;
            }else{
                if(floor == true){
                    number = Math.floor(number / 100) / 10;
                }else{
                    number = Math.ceil(number / 100) / 10;
                }
                array_length++;
            }
        }
        let string:string = number + display[array_length];
        return string;
    }

    /**
     * 时间戳转换时间
     * @param time 时间戳
     */
    time_stamp_to_time(time: number){
        let the_Date = new Date(time);
        let year = the_Date.getFullYear();
        let month = the_Date.getMonth()+1;
        let date = the_Date.getDate();
        let hour = the_Date.getHours();
        let minute = the_Date.getMinutes();
        let second = the_Date.getSeconds();
        return {year,month,date,hour,minute,second}
    }

    /**
     * 上报事件的封装方法
     * @param node 上报的节点(自己)
     * @param event_name 上报的名字
     * @param data 上报的信息
     */
    event_custom(node: cc.Node, event_name: string, data?: any){
        let event = new cc.Event.EventCustom(event_name, true);
        event.setUserData(
            data,
        );
        node.dispatchEvent(event);
    }












    
    /**
     * banner广告组件
     */
    private bannerAd: any[] = null;

    /**
     * 加载banner广告
     */
    addBannerAd() {
        if(cc.sys.platform == cc.sys.DESKTOP_BROWSER){
            return;
        }
        this.closeBannerAd();

        let a = [
            "adunit-96b833c6e585d62c",
        ]

        let bannerAd = [];

        //广告的规格
        let width1 = wx.getSystemInfoSync().screenWidth;

        for(let i = 0; i < a.length; i++){

            bannerAd[i] = wx.createBannerAd({
                adUnitId: a[i],
                style: {
                    left: 0,//(cw - 300) / 2,
                    top: 0,//ch - 300 * 23 / 80,
                    width: width1,//300,
                },
                adIntervals: 30,
            })
            
            //bannerAd.show();
            bannerAd[i].onError(function(errCode){
                console.error("流量组报错:",errCode);
            });
            bannerAd[i].onResize(() => {
                let realHeight = bannerAd[i].style.realHeight;
                let a = wx.getSystemInfoSync().screenHeight - realHeight;
                a = a - 20;
                bannerAd[i].style.top = a;
            })
    
            bannerAd[i].onLoad(() => {
                this.bannerAd = bannerAd;
            })
        }
    }

    /**
     * 清除所有的banner广告
     */
    closeBannerAd() {
        if(this.bannerAd){
            for(let i = 0; i < this.bannerAd.length; i++){
                this.bannerAd[i].destroy();
            }
        }
    }

    //隐藏banner广告
    HideBannerAd = function(){
        if(this.bannerAd){
            for(let i = 0; i < this.bannerAd.length; i++){
                this.bannerAd[i].hide();
            }
        }
    }

    /**
     * 显示对应id得banner广告
     * @param id 广告id，当广告数量只有1个时，可以不传
     */
    ShowBannerAd(id?: string){
        if(this.bannerAd == null){
            console.error("广告未构建完成");
            return
        }
        if(cc.sys.platform == cc.sys.DESKTOP_BROWSER){
            return
        }
        if(id == null){
            this.bannerAd[0].show();
            return
        }
        if(this.bannerAd){
            for(let i = 0; i < this.bannerAd.length; i++){
                if(this.bannerAd[i]){
                    if(this.bannerAd[i].adUnitId == id){
                        this.bannerAd[i].show();
                        return;
                    }
                }
            }
        }
        console.error("----没有对应banner广告----");
        this.addBannerAd();
    }

    private on_video: boolean = false;

    // 视频广告
    show_VideoAd(id: string, callback?: Function) {
        if(cc.sys.platform == cc.sys.DESKTOP_BROWSER){
            if(callback){
                callback();
            }
            return
        }else{
            if(this.on_video == false){
                this.on_video = true;
                setTimeout(() => {
                    this.on_video = false;
                },3000);
            }else{
                console.log("连续点击，不执行任何操作");
                return;
            }
        }
        let self = this;
        let rewardedVideoAd = wx.createRewardedVideoAd({ adUnitId: id });
        rewardedVideoAd.onError(function(err){
            console.error("视频广告报错",err,",",err.errCode);
            rewardedVideoAd.offClose();
            self.share_function();
        });
        rewardedVideoAd.load().then(() => {
            rewardedVideoAd.show()
        });
        rewardedVideoAd.onClose(res => {
        // 小于 2.1.0 的基础库版本，res 是一个 undefined
            if (res && res.isEnded || res === undefined) {
                // 正常播放结束，可以下发游戏奖励
                if (callback) {
                    callback();
                }
                rewardedVideoAd.offClose();
            }
            else {
                rewardedVideoAd.offClose();
                console.log("提早退出看视频");
            }
        })
    }

    private sdk_number: number = 0;

    /**
     * sdk切换视频和分享
     */
    sdk_video_share(id: string, callback?: Function){
        if(cc.sys.platform == cc.sys.DESKTOP_BROWSER){//模拟器环境，默认成功
            if(callback){
                callback();
            }
            return
        }
        // if(data_manager.Instance.sdk_data_bool == true){//sdk拿到数据了
        //     if(this.sdk_number < data_manager.Instance.sv.length){
        //         if(data_manager.Instance.sv[this.sdk_number] == '1'){//看视频
        //             this.show_VideoAd(id,callback);
        //         }else if(data_manager.Instance.sv[this.sdk_number] == '2'){
        //             this.share_function(callback);
        //         }
        //         this.sdk_number++;
        //     }else{
        //         this.sdk_number = 0;
        //         this.sdk_video_share(id,callback);
        //     }
        // }else{//sdk没拿到数据,默认播放视频
        //     this.show_VideoAd(id,callback);
        // }
    }

    /**
     * 封装打开单双曝光的方法
     */
    show_danshuang_banner(node: cc.Node, id?: number, bool?: boolean){
        let event = new cc.Event.EventCustom('show_danshuang_banner', true);
        let data = {
            id: id,
            bool: bool,
        }
        event.setUserData(
            data,
        );
        node.dispatchEvent(event);
    }

    /**
     * 封装的隐藏单双曝光的方法
     */
    hide_danshuang_banner(node){
        let event = new cc.Event.EventCustom('hide_danshuang_banner', true);
        let data = {
        }
        event.setUserData(
            data,
        );
        node.dispatchEvent(event);
    }

    /**
     * 非微信小游戏的网络请求
     * @param api 地址
     * @param 
     */
    request(api:string, data: any, callback?: Function, fail_callback?: Function){
        let url = ip + api;
        let dataStr = this.formatParams(data);//转成可以被后端确认的数

        let xhr = new XMLHttpRequest();
        xhr.onreadystatechange = function(){
            //判断有问题，不需要判断小于400，如果出错，要爆错出来
            if (xhr.readyState == 4 && xhr.status == 200) {
                let response = null
                if(xhr.responseText!=""){
                    response=JSON.parse(xhr.responseText);
                }
                if(response.code == 0){
                    if(callback){
                        callback(response);
                    }
                }else{
                    if(fail_callback){
                        fail_callback(response);
                    }
                }
            }else if(xhr.readyState == 4 && xhr.status != 200){
                let err = {url: url, readyState: xhr.readyState, status: xhr.status, data: dataStr};
                let response = null
                console.error("Server Some thing go wrong == ", err);
                if(fail_callback){
                    fail_callback(err);
                }
            }
        }

        xhr.open("post", url, true);
        
        // console.log("xml sending dataStr:",dataStr);
        xhr.setRequestHeader('Content-Type', 'application/x-www-form-urlencoded');
        xhr.send(dataStr);
    };

    private formatParams(obj):string{
        let query = '';
        let name, value, fullSubName, subName, subValue, innerObj, i;

        for (name in obj) {
            value = obj[name];

            if (value instanceof Array) {
                for (i = 0; i < value.length; ++i) {
                    subValue = value[i];
                    fullSubName = name + '[]' ;//+ '[' + i + ']';
                    innerObj = {};
                    innerObj[fullSubName] = subValue;
                    query += this.formatParams(innerObj) + '&';
                }
            } else if (value instanceof Object) {
                for (subName in value) {
                    subValue = value[subName];
                    fullSubName = name + '[' + subName + ']';
                    innerObj = {};
                    innerObj[fullSubName] = subValue;
                    query += this.formatParams(innerObj) + '&';
                }
            } else if (value !== undefined && value !== null) {
                query += encodeURIComponent(name) + '=' + encodeURIComponent(value) + '&';
            }
        }
        return query.length ? query.substr(0, query.length - 1) : query;
    };

    // /**
    //  * 定向的随机用户，并获取和保存数据
    //  */
    // test_player(callback?: Function){
    //     this.token = cc.sys.localStorage.getItem('token');
    //     let the_name = '';
    //     if(this.token == null || this.token == ''){
    //         for(let i = 0; i < 20; i++){
    //             let number = this.test_string_array[Math.floor(Math.random() * this.test_string_array.length)];
    //             the_name = the_name + number;
    //         }
    //         this.request('demo_login', {name: the_name}, (res) => {
    //             this.token = res.data;
    //             cc.sys.localStorage.setItem('token',this.token);
    //             this.request('get_userinfo', {token: this.token}, (res) => {
    //                 data_manager.Instance.all_data = res.data;
    //                 if(callback){
    //                     callback();
    //                 }
    //             })
    //         })
    //     }else{
    //         this.request('get_userinfo', {token: this.token}, (res) => {
    //             data_manager.Instance.all_data = res.data;
    //             console.log('所有的用户信息',data_manager.Instance.all_data);
    //             if(callback){
    //                 callback();
    //             }
    //         })
    //     }
    // }

    test_string_array = ['0','1','2','3','4','5','6','7','8','9','0','a','b','c','d','e','f',
            'g','h','i','j','k','l','n','m','o','p','q','r','s','t','u','v','w','x','y','z'];
}
